﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using Pibby.Core.Persistence;
using System.Xml.Serialization;

using dogd;

namespace Pibby.Core
{
	public abstract class Identifiable : IEquatable<Identifiable>, IIdentifiable
	{
		#region Attributes

		private string _guid;

		#endregion

		#region Constructors

		protected Identifiable()
		{
			this.PrimaryKey = new Key();
		}

		protected Identifiable(string id)
			: this()
		{
			this._guid = id;
		}

		#endregion 

		public override string ToString()
		{
			return this.Id;
		}

		#region Properties

		public string Id
		{
			get 
			{ 
				if (string.IsNullOrEmpty(this._guid))
					this._guid = Guid.NewGuid().ToString();

				return this._guid; 
			}

			set
			{
				if (!string.IsNullOrEmpty(this._guid))
					throw new ArgumentException(Resources.Identifiable_IdCannotBeSetMoreThanOnceError, "value");

				this._guid = value;
			}
		}

		[LookupColumn("Guid")]
		public string PersistableGuid
		{
			get { return "{" + this.Id + "}"; }
			set
			{
				if (value.StartsWith("{", StringComparison.OrdinalIgnoreCase))
					this.Id = value.Substring(1, value.Length - 2);
				else
					this.Id = value;
			}
		}

        [XmlIgnore]
		public Key PrimaryKey
		{
			get;
			private set;
		}

		public bool Equals(Identifiable other)
		{
			if (other == null)
			{
				return false;
			}
		
			return StringComparer.Ordinal.Equals(Id, other.Id);
		}

		public override int GetHashCode()
		{
			return this.Id.GetHashCode();
		}

		public override bool Equals(object obj)
		{
			var id = obj as Identifiable;
			
			if (id != null)
				return this.Equals(id);

			return false;
		}

		#endregion

	}
}
